4: Create Connection
Now that the Issuer has a credential definition, they can start issuing
credentials. However, in order to do that, they first needs to create a
connection to the holder. There are multiple ways to create connections. We will
use the /v1/connections/ endpoints in these examples.
Create connection between Issuer and Holder
As the Issuer we create a connection invitation.
Note: The
multi_usefield indicates that theinvitation urlcan be accepted by multiple tenants to create connections with them.use_public_didcan be set to true for issuers making the invitation, because they are onboarded with a public did, but it's not necessary. It will simply allow the holder to validate the did of the issuer, as they will then be able to see it in the connection record.
curl -X 'POST' \
'https://cloudapi.test.didxtech.com/tenant/v1/connections/create-invitation' \
-H 'accept: application/json' \
-H 'Content-Type: application/json' \
-H 'x-api-key: tenant.<Issuer token>' \
-d '{
"alias": "Issuer <> Holder",
"multi_use": false,
"use_public_did": false
}'
Response:
{
"connection_id": "c78f9423-370e-4800-a48e-962456083943",
"invitation": {
"@id": "6a86e6c7-af25-4e5d-87fe-b42f559b13b9",
"@type": "https://didcomm.org/connections/1.0/invitation",
"did": null,
"imageUrl": "https://upload.wikimedia.org/wikipedia/commons/7/70/Example.png",
"label": "Demo Issuer",
"recipientKeys": ["91ZNSpDgVoV12kHcmUqyp1JmGeKE7oGi9NFd2WMzKt4X"],
"routingKeys": null,
"serviceEndpoint": "http://governance-multitenant-agent:3020"
},
"invitation_url": "http://governance-multitenant-agent:3020?c_i=eyJAdHlwZSI6ICJodHRwczovL2RpZGNvbW0ub3JnL2Nvbm5lY3Rpb25zLzEuMC9pbnZpdGF0aW9uIiwgIkBpZCI6ICI2YTg2ZTZjNy1hZjI1LTRlNWQtODdmZS1iNDJmNTU5YjEzYjkiLCAic2VydmljZUVuZHBvaW50IjogImh0dHA6Ly9nb3Zlcm5hbmNlLW11bHRpdGVuYW50LWFnZW50OjMwMjAiLCAiaW1hZ2VVcmwiOiAiaHR0cHM6Ly91cGxvYWQud2lraW1lZGlhLm9yZy93aWtpcGVkaWEvY29tbW9ucy83LzcwL0V4YW1wbGUucG5nIiwgInJlY2lwaWVudEtleXMiOiBbIjkxWk5TcERnVm9WMTJrSGNtVXF5cDFKbUdlS0U3b0dpOU5GZDJXTXpLdDRYIl0sICJsYWJlbCI6ICJEZW1vIElzc3VlciJ9"
}
The Holder accepts the connection by using the invitation object above, and
by posting to the /v1/connections/accept-invitation endpoint.
Note: the
invitationobject can also be obtained by decoding the base64 payload in the invitation_url, after thec_i=indicator.
curl -X 'POST' \
'https://cloudapi.test.didxtech.com/tenant/v1/connections/accept-invitation' \
-H 'accept: application/json' \
-H 'Content-Type: application/json' \
-H 'x-api-key: tenant.<Holder token>' \
-d '{
"alias": "Holder <> Issuer",
"use_existing_connection": false,
"invitation": {
"@id": "6a86e6c7-af25-4e5d-87fe-b42f559b13b9",
"@type": "https://didcomm.org/connections/1.0/invitation",
"did": null,
"imageUrl": "https://upload.wikimedia.org/wikipedia/commons/7/70/Example.png",
"label": "Demo Issuer",
"recipientKeys": [
"91ZNSpDgVoV12kHcmUqyp1JmGeKE7oGi9NFd2WMzKt4X"
],
"routingKeys": null,
"serviceEndpoint": "http://governance-multitenant-agent:3020"
}
}'
Response:
{
"alias": "Holder <> Issuer",
"connection_id": "ac3b0d56-eb33-408a-baeb-0370164d47ae",
"connection_protocol": "connections/1.0",
"created_at": "2023-11-20T09:56:41.437966Z",
"error_msg": null,
"invitation_key": "91ZNSpDgVoV12kHcmUqyp1JmGeKE7oGi9NFd2WMzKt4X",
"invitation_mode": "once",
"invitation_msg_id": "6a86e6c7-af25-4e5d-87fe-b42f559b13b9",
"my_did": "MYhLew4uq58mou8SCTNFYp",
"state": "request-sent",
"their_did": null,
"their_label": "Demo Issuer",
"their_public_did": null,
"their_role": "inviter",
"updated_at": "2023-11-20T09:56:41.472385Z"
}
Both of the tenants can listen to Webhook/SSE events to track the progress of
the connection being made. Once the state is completed, the connection is
made. This can also be asserted by fetching connection records for the holder or
issuer, and validating that their connection has transitioned to state:
completed.
Below is an example of a webhook event indicating the completed state.
NOTE: The field IDs will be unique to each tenant i.e. the
connection_idof theIssuerwill be different from that of theHolder, even though they refer to the same connection.
{
"wallet_id": "4e0c70fb-f2ad-4f59-81f3-93d8df9b977a",
"topic": "connections",
"origin": "multitenant",
"payload": {
"alias": "Holder <> Issuer",
"connection_id": "359b30a2-c98d-4c00-b318-8185d1d0e64d",
"connection_protocol": "connections/1.0",
"created_at": "2023-11-16T07:57:18.451554Z",
"error_msg": null,
"invitation_key": "8Vd5YSVBw5p6BJ8nHngZ2UcCKBmTSxQHoNWfaBQJXW5U",
"invitation_mode": "once",
"invitation_msg_id": "0ef82415-20ba-4d1e-818b-92a70355ec6e",
"my_did": "NXk4JkDpFff4MpnTwvn1Wa",
"state": "completed",
"their_did": "LN2WMyrMFH74L1GTkSteka",
"their_label": "Demo Issuer",
"their_public_did": null,
"their_role": "inviter",
"updated_at": "2023-11-16T07:57:18.748560Z"
}
}
Next: 5: Issue a Credential